package com.example.studentknowledge.service;

import com.example.studentknowledge.entity.Article;
import com.example.studentknowledge.entity.Attachment;
import com.example.studentknowledge.entity.User;
import com.example.studentknowledge.repository.AttachmentRepository;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.Pageable;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.multipart.MultipartFile;

import java.io.File;
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
import java.util.List;
import java.util.Optional;
import java.util.UUID;

/**
 * 附件服务类
 */
@Service
@Transactional
public class AttachmentService {
    
    @Autowired
    private AttachmentRepository attachmentRepository;
    
    @Value("${file.upload.path:uploads}")
    private String uploadPath;
    
    @Value("${file.max.size:10485760}") // 10MB
    private long maxFileSize;
    
    private static final String[] ALLOWED_EXTENSIONS = {
        ".pdf", ".doc", ".docx", ".xls", ".xlsx", ".ppt", ".pptx",
        ".txt", ".zip", ".rar", ".7z", ".jpg", ".jpeg", ".png", ".gif"
    };
    
    /**
     * 上传附件
     */
    public Attachment uploadAttachment(MultipartFile file, User uploader, Article article) throws IOException {
        // 验证文件
        validateFile(file);
        
        // 生成文件名
        String originalFilename = file.getOriginalFilename();
        String extension = getFileExtension(originalFilename);
        String filename = UUID.randomUUID().toString() + extension;
        
        // 创建上传目录
        String dateDir = LocalDateTime.now().format(DateTimeFormatter.ofPattern("yyyy/MM/dd"));
        String uploadDir = uploadPath + File.separator + dateDir;
        Path uploadDirPath = Paths.get(uploadDir);
        if (!Files.exists(uploadDirPath)) {
            Files.createDirectories(uploadDirPath);
        }
        
        // 保存文件
        String filePath = uploadDir + File.separator + filename;
        Path targetPath = Paths.get(filePath);
        Files.copy(file.getInputStream(), targetPath);
        
        // 创建附件记录
        Attachment attachment = new Attachment();
        attachment.setOriginalName(originalFilename);
        attachment.setFileName(filename);
        attachment.setFilePath(filePath);
        attachment.setFileSize(file.getSize());
        attachment.setFileType(getFileType(extension));
        attachment.setUploader(uploader);
        attachment.setArticle(article);
        
        return attachmentRepository.save(attachment);
    }
    
    /**
     * 下载附件
     */
    public void downloadAttachment(Long id) {
        Attachment attachment = attachmentRepository.findById(id)
                .orElseThrow(() -> new RuntimeException("附件不存在"));
        
        // 增加下载次数
        attachmentRepository.incrementDownloadCount(id);
    }
    
    /**
     * 根据ID查找附件
     */
    public Optional<Attachment> findById(Long id) {
        return attachmentRepository.findById(id);
    }
    
    /**
     * 根据文章获取附件
     */
    public List<Attachment> getAttachmentsByArticle(Article article) {
        return attachmentRepository.findByArticleOrderByCreatedAtDesc(article);
    }
    
    /**
     * 根据上传者获取附件
     */
    public Page<Attachment> getAttachmentsByUploader(User uploader, Pageable pageable) {
        return attachmentRepository.findByUploaderOrderByCreatedAtDesc(uploader, pageable);
    }
    
    /**
     * 根据文件类型获取附件
     */
    public Page<Attachment> getAttachmentsByFileType(String fileType, Pageable pageable) {
        return attachmentRepository.findByFileTypeOrderByCreatedAtDesc(fileType, pageable);
    }
    
    /**
     * 搜索附件
     */
    public Page<Attachment> searchAttachments(String keyword, Pageable pageable) {
        return attachmentRepository.findByFileNameContaining(keyword, pageable);
    }
    
    /**
     * 获取热门附件
     */
    public List<Attachment> getPopularAttachments(int limit) {
        return attachmentRepository.findPopularAttachments(Pageable.ofSize(limit));
    }
    
    /**
     * 获取最新附件
     */
    public List<Attachment> getLatestAttachments(int limit) {
        return attachmentRepository.findLatestAttachments(Pageable.ofSize(limit));
    }
    
    /**
     * 删除附件
     */
    public void deleteAttachment(Long id) throws IOException {
        Attachment attachment = attachmentRepository.findById(id)
                .orElseThrow(() -> new RuntimeException("附件不存在"));
        
        // 删除物理文件
        Path filePath = Paths.get(attachment.getFilePath());
        if (Files.exists(filePath)) {
            Files.delete(filePath);
        }
        
        // 删除数据库记录
        attachmentRepository.deleteById(id);
    }
    
    /**
     * 统计上传者的附件数
     */
    public Long countByUploader(User uploader) {
        return attachmentRepository.countByUploader(uploader);
    }
    
    /**
     * 统计文章的附件数
     */
    public Long countByArticle(Article article) {
        return attachmentRepository.countByArticle(article);
    }
    
    /**
     * 验证文件
     */
    private void validateFile(MultipartFile file) {
        if (file.isEmpty()) {
            throw new RuntimeException("文件不能为空");
        }
        
        if (file.getSize() > maxFileSize) {
            throw new RuntimeException("文件大小不能超过 " + (maxFileSize / 1024 / 1024) + "MB");
        }
        
        String filename = file.getOriginalFilename();
        if (filename == null || filename.trim().isEmpty()) {
            throw new RuntimeException("文件名不能为空");
        }
        
        String extension = getFileExtension(filename).toLowerCase();
        boolean isAllowed = false;
        for (String allowedExt : ALLOWED_EXTENSIONS) {
            if (allowedExt.equals(extension)) {
                isAllowed = true;
                break;
            }
        }
        
        if (!isAllowed) {
            throw new RuntimeException("不支持的文件类型: " + extension);
        }
    }
    
    /**
     * 获取文件扩展名
     */
    private String getFileExtension(String filename) {
        if (filename == null || filename.lastIndexOf('.') == -1) {
            return "";
        }
        return filename.substring(filename.lastIndexOf('.'));
    }
    
    /**
     * 根据扩展名获取文件类型
     */
    private String getFileType(String extension) {
        extension = extension.toLowerCase();
        
        if (".pdf".equals(extension)) {
            return "PDF";
        } else if (".doc".equals(extension) || ".docx".equals(extension)) {
            return "Word";
        } else if (".xls".equals(extension) || ".xlsx".equals(extension)) {
            return "Excel";
        } else if (".ppt".equals(extension) || ".pptx".equals(extension)) {
            return "PowerPoint";
        } else if (".txt".equals(extension)) {
            return "文本";
        } else if (".zip".equals(extension) || ".rar".equals(extension) || ".7z".equals(extension)) {
            return "压缩包";
        } else if (".jpg".equals(extension) || ".jpeg".equals(extension) || ".png".equals(extension) || ".gif".equals(extension)) {
            return "图片";
        } else {
            return "其他";
        }
    }
}